package com.diors.commons.network;

import java.net.InetSocketAddress;
import java.util.concurrent.Executors;

import org.apache.log4j.Logger;
import org.jboss.netty.bootstrap.ClientBootstrap;
import org.jboss.netty.buffer.ChannelBuffer;
import org.jboss.netty.channel.Channel;
import org.jboss.netty.channel.ChannelFactory;
import org.jboss.netty.channel.ChannelFuture;
import org.jboss.netty.channel.ChannelPipeline;
import org.jboss.netty.channel.socket.nio.NioClientSocketChannelFactory;

/**
 * 抽象连接服务器
 * @author	darren.ouyang <ouyang.darren@gmail.com>
 * @date	2013-10-21
 * @version 1.0
 * @copyright Copyright (c) 2013, darren.ouyang
 */
public abstract class AbstractClient 
{
	
	static final Logger log = Logger.getLogger(AbstractServer.class);
	
	/* 处理对象 */
	protected NetworkHandler<? extends AbstractConnection> handler;
	
	/* 服务器绑定的端口地址 */
	protected InetSocketAddress address;
	
	protected Channel channel;
	
	public Channel init ()
	{
		ChannelFactory factory = new NioClientSocketChannelFactory(
				Executors.newCachedThreadPool(), Executors.newCachedThreadPool());
		ClientBootstrap bootstrap = new ClientBootstrap(factory);
		
		/* 为每个连接设置成相同的Handler对象 */
		ChannelPipeline pipline = bootstrap.getPipeline();
		pipline.addLast("handler", handler);

		/* 设置socket选项 */
		/* child意味配置项适用我们接收到的通道实例,而不是ServerSocketChannel实例 */
		bootstrap.setOption("tcpNoDelay", true);  	// 提高数据的实时响应性,数据不延迟
	    bootstrap.setOption("keepAlive", true);  	// ack探测包 是否继续维持该socket
		
	    /* 返回了一个绑定了本地地址的服务端Channel通道对象,并注册到管道集合中 */
	    ChannelFuture cf = bootstrap.connect(address);
	    channel = cf.awaitUninterruptibly().getChannel();
		
		log.info(new StringBuilder("服务器启动监听IP[").append(address.getHostString()).
				append("]端口[").append(address.getPort()).append("]").toString());
		
		return channel;
	}

	public void write (ChannelBuffer channelBuffer)
	{
		channel.write(channelBuffer);
	}
}

